<?php
#
# dmBridge: a data access framework for CONTENTdm(R)
#
# Copyright © 2009, 2010, 2011 Board of Regents of the Nevada System of Higher
# Education, on behalf of the University of Nevada, Las Vegas
#

/**
 * @author Alex Dolski <alex.dolski@unlv.edu>
 * @license http://www.opensource.org/licenses/mit-license.php
 */
class DMTemplateSet extends DMModel {

	/** @var Array of DMCollections */
	private $authorized_collections = array();
	/** @var DMCollection */
	private $default_collection;
	/** @var array of DMDCElement objects */
	private $grid_view_fields = array();
	/** @var boolean */
	private $has_been_loaded = false;
	/** @var string */
	private $name;
	/** @var int */
	private $num_results_per_page;
	/** @var int */
	private $num_tile_columns;
	/** @var int */
	private $id;
	/** @var string */
	private $pathname;
	/** @var Array of DMTemplates */
	private $templates = array();


	/**
	 * If $id is supplied and is a valid template set ID from the data store,
	 * automatically populates the set's properties from the data store.
	 * Otherwise instantiates an empty DMTemplateSet object.
	 *
	 * @param int id
	 * @throws DMUnavailableModelException
	 * @since 0.1
	 */
	public function __construct($id = null) {
		if (!is_null($id) && $id >= 0 && round($id) == $id) {
			$this->setID($id);
			$this->load();
		}
	}

	/**
	 * Equivalent to calling getName(). The return value of this method is not
	 * stable and should not be relied upon.
	 *
	 * @return The template set's name
	 * @since 0.3
	 */
	public function __toString() {
		return (string) $this->getName();
	}

	/**
	 * @param DMCollection c
	 * @since 0.3
	 */
	public function addAuthorizedCollection(DMCollection $c) {
		$match = false;
		foreach ($this->authorized_collections as $col) {
			if ($col->equals($c)) {
				$match = true;
			}
		}
		if (!$match) {
			$this->authorized_collections[] = $c;
		}
	}

	/**
	 * @return array of DMCollection objects
	 * @since 0.3
	 */
	public function getAuthorizedCollections() {
		return $this->authorized_collections;
	}

	/**
	 * @return void
	 * @since 0.3
	 */
	public function unsetAuthorizedCollections() {
		$this->authorized_collections = array();
	}

	/**
	 * @param DMCollection c
	 * @return Boolean
	 * @since 0.3
	 * @see DMCollection::isAccessibleByTemplateSet()
	 */
	public function isAuthorizedToViewCollection(DMCollection $c) {
		$aliases = array();
		$authorized = $this->getAuthorizedCollections();
		if (count($authorized) < 1) {
			return true;
		}
		foreach ($authorized as $tmp) {
			$aliases[] = $tmp->getAlias();
		}
		return (in_array($c->getAlias(), $aliases));
	}

	/**
	 * Deletes the DMTemplateSet object from the data store and unsets the
	 * DMTemplateSet object.
	 *
	 * @return void
	 * @throws DMDataStoreException
	 * @deprecated
	 */
	public function delete() {
		DMConfigXML::getInstance()->deleteTemplateSet($this);
		unset($this);
	}

	private function load() {
		if (!$this->has_been_loaded) {
			DMConfigXML::getInstance()->loadTemplateSet($this);
			$this->has_been_loaded = true;
		}
	}

	/**
	 * @return DMCollection
	 * @since 0.3
	 */
	public function getDefaultCollection() {
		return $this->default_collection;
	}

	/**
	 * @param DMCollection col
	 * @since 0.3
	 */
	public function setDefaultCollection(DMCollection $col) {
		if ($col->getAlias() == "/dmdefault") {
			throw new DMIllegalArgumentException(
				DMLocalizedString::getString("INVALID_COLLECTION"));
		}
		$this->default_collection = $col;
	}

	/**
	 * Returns the template-specific error DMTemplate, or the default dmBridge
	 * error DMTemplate if that doesn't exist.
	 *
	 * @return DMTemplate
	 * @since 2.0
	 */
	public function getErrorTemplate() {
		$tpl = "/templates/error/view.html.php";
		$system = "/../system/error.html.php";
		$check_path = $_SERVER['DOCUMENT_ROOT'] . $this->getPath() . $tpl;
		$path = (file_exists($check_path)) ? $tpl : $system;
		return new DMTemplate($this, $path);
	}

	/**
	 * @param DMDCElement f
	 */
	public function addGridViewField(DMDCElement $f) {
		$this->grid_view_fields[] = $f;
	}

	/**
	 * @return array array of DMDCElement objects
	 */
	public function getGridViewFields() {
		return $this->grid_view_fields;
	}

	/**
	 * @return void
	 */
	public function unsetGridViewFields() {
		$this->grid_view_fields = array();
	}

	/**
	 * @return int
	 * @since 0.3
	 */
	public function getID() {
		return $this->id;
	}

	/**
	 * @param int id
	 * @since 0.3
	 */
	public function setID($id) {
		$this->id = $id;
	}

	/**
	 * @return string
	 * @since 0.3
	 */
	public function getName() {
		return $this->name;
	}

	/**
	 * @param string str
	 * @since 0.3
	 */
	public function setName($str) {
		$this->name = (string) $str;
	}

	/**
	 * @return int The number of results that are to appear in results view.
	 */
	public function getNumResultsPerPage() {
		return $this->num_results_per_page;
	}

	/**
	 * @param int rpp The number of results that are to appear in results view.
	 */
	public function setNumResultsPerPage($rpp) {
		$this->num_results_per_page = (int) $rpp;
	}

	/**
	 * @return int
	 */
	public function getNumTileViewColumns() {
		return $this->num_tile_columns;
	}

	/**
	 * @param int int
	 */
	public function setNumTileViewColumns($int) {
		$this->num_tile_columns = (int) $int;
	}

	/**
	 * @return void
	 */
	public function unsetNumTileViewColumns() {
		$this->num_tile_columns = null;
	}

	/**
	 * @return string The path to the template set, relative to the web
	 * server's document root.
	 */
	public function getPath() {
		if ($this->pathname) {
			return $this->pathname;
		}
		return dirname($_SERVER['PHP_SELF']) . "/templates/"
				. strtolower(
					DMString::paranoid(
						str_replace(' ', '_', $this->getName()),
						array("_", "-")));
	}

	/**
	 * Overrides the template set's pathname.
	 *
	 * @param string path
	 */
	public function setPath($path) {
		$this->pathname = $path;
	}

	/**
	 * @return array Array of DMTemplate objects
	 * @since 2.0
	 */
	public function getTemplates() {
		if (!count($this->templates)) {
			$all_templates = array(
				'/templates/error/view.html.php',
				'/templates/favorite/index.html.php',
				'/templates/object/no_results.html.php',
				'/templates/object/results.html.php',
				'/templates/object/results_faceted.html.php',
				'/templates/object/view_compound.html.php',
				'/templates/object/view_simple.html.php',
				'/templates/search/index.html.php',
				'/templates/user/login.html.php'
			);
			foreach ($all_templates as $relative_pathname) {
				$this->templates[] = new DMTemplate($this,
					$relative_pathname);
			}
		}
		return $this->templates;
	}

	/**
	 * @param string pathname Pathname relative to the root of the template set
	 * folder
	 * @return DMTemplate
	 * @since 2.0
	 */
	public function getTemplateAtPathname($pathname) {
		foreach ($this->getTemplates() as $tpl) {
			if ($tpl->getRelativePathname() == $pathname) {
				return $tpl;
			}
		}
		return null;
	}

}
